package nl.txproductions.twitterclient.threading;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

import nl.txproductions.twitterclient.http.Request;
import nl.txproductions.twitterclient.http.Response;
import nl.txproductions.twitterclient.model.JsonParser;
import nl.txproductions.twitterclient.model.Message;
import ca.odell.glazedlists.EventList;

public class CustomThreadPoolExecutor implements Runnable {

	public static final String TWITTER_URL = "http://twitter.com/statuses/public_timeline.json";

	private EventList<Message> eventList;
	private ExecutorService executor;

	public CustomThreadPoolExecutor(EventList<Message> eventList) {
		this.eventList = eventList;

		this.executor = Executors.newFixedThreadPool(1);
	}

	private void doExecute() throws MalformedURLException,
			InterruptedException, ExecutionException {

		try {
			Future<Response> response = this.executor.submit(new Request(
					new URL(TWITTER_URL)));

			InputStream body = response.get().getBody();

			StringBuilder builder = new StringBuilder();
			BufferedReader reader = null;
			try {
				reader = new BufferedReader(new InputStreamReader(body));
				String line = null;

				while ((line = reader.readLine()) != null) {
					builder.append(line);
				}

				List<Message> messages = new JsonParser()
						.getMessagesFromJson(builder.toString());

				Collections.reverse(messages);

				this.addMessages(messages);

			} catch (IOException ex) {
				System.out.println(ex);
			} finally {
				if (reader != null) {
					try {
						reader.close();
					} catch (IOException ex) {
						System.out.println("BufferedReader cannot be closed.");
					}
				}
			}
		} catch (Exception ex) {
			System.out.println("Caught Exception: " + ex);
		}
	}

	private void addMessages(List<Message> messages) {
		this.eventList.getReadWriteLock().writeLock().lock();
		try {
			this.eventList.clear();
			this.eventList.addAll(messages);
		} finally {
			this.eventList.getReadWriteLock().writeLock().unlock();
		}
	}

	@Override
	public void run() {
		try {
			while (true) {
				this.doExecute();
				Thread.sleep(3000);
			}
		} catch (MalformedURLException e) {
			System.out.println(e);
		} catch (InterruptedException e) {
			System.out.println(e);
		} catch (ExecutionException e) {
			System.out.println(e);
		}
	}

	public void shutdown() {
		this.executor.shutdown();
	}
}